#ifndef SVECTOR_HPP_
#define SVECTOR_HPP_

/* The following code example is taken from the book
 * "C++ Templates - The Complete Guide"
 * by David Vandevoorde and Nicolai M. Josuttis, Addison-Wesley, 2002
 *
 * (C) Copyright David Vandevoorde and Nicolai M. Josuttis 2002.
 * Permission to copy, use, modify, sell and distribute this software
 * is granted provided this copyright notice appears in all copies.
 * This software is provided "as is" without express or implied
 * warranty, and with no claim as to its suitability for any purpose.
 */
#include <stddef.h>
#include <cassert>
#include "usertypes.hpp"

template<typename T>
class SVector {
public:
  // create array with initial size
  explicit SVector (myindex s)
    : storage(new T[s]), storage_size(s) 
  {
    init();
  }

  // copy constructor
  SVector (SVector<T> const& orig)
    : storage(new T[orig.size()]), storage_size(orig.size()) 
  {
    copy(orig);
  }

  void freemem()
  {
    storage_size = 0;
    delete[] storage;
  }


  // destructor: free memory
  ~SVector() 
  {
    freemem ();
  }

  // assignment operator
  SVector<T>& operator= (SVector<T> const& orig) 
  {
    if (&orig!=this)
      copy(orig);
  
    return *this;
  }

  // return size
  myindex size() const {
    return storage_size;
  }

  // index operator for constants and variables
  T operator[] (myindex idx) const 
  {
    return storage[idx];
  }
  
  T& operator[] (myindex idx) 
  {
    return storage[idx];
  }

protected:
  // init values with default constructor
  void init() 
  {
    for (myindex idx = 0; idx<size(); ++idx)
      storage[idx] = T();
  }
  // copy values of another array
  void copy (SVector<T> const& orig) 
  {
    assert(size()==orig.size());
    for (myindex idx = 0; idx<size(); ++idx)
      storage[idx] = orig.storage[idx];
  }

private:
  T*     storage;       // storage of the elements
  myindex storage_size;  // number of elements
};

#endif // SVECTOR_HPP_
